﻿using System;
using System.Xml;
using System.Xml.Schema;
using System.Xml.Serialization;
using System.Reflection;

namespace ButtonBuilder.Plugin
{
    public class PluginSerializer : IXmlSerializable
    {
        #region Static
        public static implicit operator PluginSerializer(Action p)
        {
            return p == null ? null : new PluginSerializer(p);
        }

        public static implicit operator Action(PluginSerializer p)
        {
            return p == null ? null : p.Action;
        }
        #endregion

        #region Constructors
        public PluginSerializer() { }

        public PluginSerializer(Action action)
        {
            Action = action;
        }
        #endregion

        #region Properties
        public Action Action
        {
            get;
            private set;
        }
        #endregion

        #region IXmlSerializable Implementation
        public XmlSchema GetSchema()
        {
            return null;
        }

        public void ReadXml(XmlReader reader)
        {
            try
            {
                Assembly plugin = Assembly.LoadFrom(reader.GetAttribute("assembly"));
                Type type = plugin.GetType(reader.GetAttribute("type"));

                reader.ReadStartElement();
                Action = (Action)new XmlSerializer(type).Deserialize(reader);
                Action.Init();

                reader.ReadEndElement();
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);

                Action = new EmptyAction();
            }
        }

        public void WriteXml(XmlWriter writer)
        {
            writer.WriteAttributeString("assembly", Action.GetType().Assembly.Location);
            writer.WriteAttributeString("type", Action.GetType().ToString());

            XmlSerializerNamespaces xmlnsEmpty = new XmlSerializerNamespaces();
            xmlnsEmpty.Add("", "");
            new XmlSerializer(Action.GetType()).Serialize(writer, Action, xmlnsEmpty);
        }
        #endregion
    }
}